import fs from 'fs';
import { join, dirname } from 'path';
import { runCommand } from '../common/utils.js';

/**
 * 写入 package.json 到工作目录
 */
async function writePackageJson(workDir, packageJSON) {
    const packageJsonPath = join(workDir, 'package.json');

    if (!fs.existsSync(workDir)) {
        fs.mkdirSync(workDir, { recursive: true });
    }

    fs.writeFileSync(packageJsonPath, JSON.stringify(packageJSON, null, 2), 'utf-8');
}

/**
 * 过滤掉本地链接依赖,不然会报错
 */
function filterLinkDependencies(deps) {
    if (!deps) return deps;

    return Object.fromEntries(
        Object.entries(deps).filter(([key, value]) =>
            !(typeof value === 'string' && value.startsWith('link:'))
        )
    );
}

/**
 * 创建 lock 文件（处理本地链接依赖）
 */
async function createLockFile(workDir) {
    const packageJsonPath = join(workDir, 'package.json');

    // 读取 package.json
    const packageJson = JSON.parse(fs.readFileSync(packageJsonPath, 'utf-8'));

    // 备份原始依赖
    const originalDependencies = { ...packageJson.dependencies };
    const originalDevDependencies = { ...packageJson.devDependencies };

    console.log('🔍 检查本地链接依赖...');

    // 过滤掉本地链接依赖
    packageJson.dependencies = filterLinkDependencies(packageJson.dependencies);
    packageJson.devDependencies = filterLinkDependencies(packageJson.devDependencies);

    // 写入临时 package.json（不含本地链接）
    fs.writeFileSync(packageJsonPath, JSON.stringify(packageJson, null, 2));

    try {
        // 只生成lock文件，不下载实际包，节省时间和磁盘空间
        // --force 强制继续安装，即使有冲突,或者失败
        // # 更温和的方式
        // npm install --package-lock-only --legacy-peer-deps
        const cmd = 'npm install --package-lock-only --force --ignore-scripts';
        console.log('🔄 生成 package-lock.json...');
        const result = await runCommand(cmd, workDir);
        console.log('✅ package-lock.json 生成成功');
        return result;
    } finally {
        // 恢复原始 package.json（包含本地链接依赖）
        const restoredPackageJson = {
            ...packageJson,
            dependencies: originalDependencies,
            devDependencies: originalDevDependencies
        };
        fs.writeFileSync(packageJsonPath, JSON.stringify(restoredPackageJson, null, 2));
        console.log('✅ 已恢复原始 package.json');
    }
}

export async function generateLock(workDir, packageJson) {
    // 1. 将 package.json 写入工作目录
    await writePackageJson(workDir, packageJson);
    // 2. 生成 lock 文件（会自动处理本地链接依赖）
    await createLockFile(workDir);
}